#ifndef __MY_VECTOR_H__
#define __MY_VECTOR_H__
#include <iostream>

template <class T>
class MyVector{
private:
    T* mData;
    int mSize;
    int mCapacity;

public:
    MyVector(int capacity = 5){
        mSize = 0;
        mCapacity = capacity;
        mData = new T[capacity];
    }

    MyVector(const MyVector& other){
        mSize = other.mSize;
        mCapacity = other.mCapacity;
        
        mData = new T[mCapacity];
        for(int i = 0; i < other.mSize; i++){
            mData[i] = other.mData[i];
        }
    }

    MyVector(const MyVector&& other){
        mSize = other.mSize;
        mCapacity = other.mCapacity;
        mData = other.mData;

        other.mData = nullptr;
        other.mSize = 0;
        other.mCapacity = 0;
    }

    MyVector& operator=(const MyVector& other){
        mSize = other.mSize;
        mCapacity = other.mCapacity;

        delete[] mData;

        mData = new T[other.mCapacity];
        for(int i = 0; i < other.mSize; i++){
            mData[i] = other.mData[i];
        }

        return *this;
    }

    MyVector& operator=(const MyVector&& other){
        mSize = other.mSize;
        mCapacity = other.mCapacity;
        delete[] mData;
        mData = other.mData;

        other.mData = nullptr;
        other.mSize = 0;
        other.mCapacity = 0;

        return *this;
    }

    T& operator[](int index){
        return mData[index];
    }

    T& at(int index){
        return mData[index];
    }

    int size(){
        return mSize;
    }

    int capacity(){
        return mCapacity;
    }

    void reserve(int capacity){
        if(capacity < mCapacity){
            return;
        }

        T* newData = new T[capacity];
        for(int i = 0; i < mSize; i++){
            newData[i] = mData[i];
        }

        delete[] mData;
        mData = newData;
        mCapacity = capacity;
    }


    void push_back(T data){
        if(mSize >= mCapacity){
            reserve(mCapacity * 2);
        }

        mData[mSize] = data;
        mSize++;
    }

    void pop_back(){
        mSize--;
    }

};


#endif